package chapter08_class

/**
 * Created with IntelliJ IDEA.
 * ClassName: Test
 * Package: chapter08_class
 * Description:
 * User: fzykd
 *
 * @Author: LQH
 *          Date: 2023-07-03
 *          Time: 12:52
 */

//特质 代替了 接口的概念
object Test09_Trait {
  //1.特质可以有抽象的属性和方法 也可以有具体的属性和方法 一个类可以混入多个特质
  //2.Scala中的trait特征 代替Java接口 第一个是补充单继承的缺陷
  def main(args: Array[String]): Unit = {
    val student = new Stu9
    student.say
    student.study
    student.dating()
    student.play

    println("-------------")

    //动态混入 在创建的实例的时候才混入这些特征
    val studentTalent = new Stu9 with Talent {
      //特征当中的抽象方法 重写使用了 override关键字 但是抽象类的重写没有override关键字
      override def dancing(): Unit = println("student is dancing")

      override def singing(): Unit = println("student is singing")
    }

    studentTalent.study
    studentTalent.play


  }
}

class Person9 {
  val name: String = "person"
  //如果定义了不赋值 就是抽象类
  val age: Int = 12

  def say: Unit = {
    println("hello from: " + name)
  }

  def increase(): Unit = {
    //这个super方法 执行的是Knowledge increase
    //前提是父类当中没有increase
    println("Person increase")
  }

}

//定义天赋
trait Talent {
  def singing(): Unit

  def dancing(): Unit
}

//定义一个特征 青年人的特征
trait Yong {

  //可以是抽象的 也 可以是非抽象的
  val age: Int = 10
  val name: String = "yong"

  def play: Unit = {
    println("yong is playing")
  }

  def dating(): Unit

}

//定义一个子类
class Stu9 extends Person9 with Yong {

  //对于这个age来说 父类是如果父类是val定义 要是重写就要使用override
  //但是特征当中定义的age又是抽象类 重写不使用override
  //都是先以父类的为主
  override val age = 100

  //父类 和 特质当中 定义了相同的属性 并且赋值 val定义的
  //当子类继承父类和特质的时候 无法分辨到底听谁的 那么子类就必须自己重写冲突的属性
  override val name: String = "student11"

  override def dating(): Unit = {
    println(s"student $name  dating ${age}")
  }

  def study = {
    println(s"student is $name is study")
  }

  //重写父类方法
  override def say: Unit = {

    super.say
    println(s"hello from student $name")
  }


}